package co.fitstart.entity.user.inbody;

import java.beans.Transient;
import java.util.Date;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

import org.apache.commons.lang3.StringUtils;
import org.hibernate.annotations.DynamicUpdate;

import com.alibaba.fastjson.annotation.JSONField;
import com.demo2do.core.utils.DateFormatUtils;
import com.demo2do.core.utils.DateUtils;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;

import co.fitstart.entity.reference.Gender;
import co.fitstart.entity.user.User;

/**
 * 
 * @author mohanlan
 *
 */
@Entity
@Table(name = ("inbody_record"))
@DynamicUpdate
@JsonIgnoreProperties(value={"hibernate_lazy_initializer","handler","fieldHandler"})
public class InbodyRecord {
    
    @Id
    @GeneratedValue
    private Long id;
    
    @ManyToOne(fetch = FetchType.LAZY, optional = true)
    @JSONField(serialize = false)
    private User user;
    
    /** 姓名 冗余字段 */
    private String name;
    
    /** 来源 */
    private String source;
    
    private Integer age;
    
    @Enumerated(EnumType.ORDINAL)
    private Gender gender;
    
    /** 用户手机号 冗余字段，用于excel表格数据匹配 */
    private String mobile;
    
    /** 体重 保留小数点后两位 */
    private Float weight;
    
    private Float weightMax;
    
    private Float weightMin;
    
    /** skeletalMuscle 骨骼肌 保留小数点后一位 */
    private Float sm;
    
    private Float smMax;
    
    private Float smMin;
    
    /** bodyFat 体脂肪 保留小数点后一位 */
    private Float bf;
    
    private Float bfMax;
    
    private Float bfMin;
    
    /** bodyFatRate 体脂率 保留小数点后一位*/
    private Float bfr;
    
    private Float bfrMax;
    
    private Float bfrMin;
    
    /** BMI值 保留小数点后一位*/
    private Float bmi;
    
    private Float bmiMax;
    
    private Float bmiMin;
    
    /** waist-hip ratio 腰臀比 保留小数点后一位*/
    private Float whr;
    
    private Float whrMax;
    
    private Float whrMin;
    
    /** basal metabolism 基础代谢 保留小数点后一位*/
    private Float bm;
    
    private Float bmMax;
    
    private Float bmMin;
    
    /** 记录测试时间 */
    private String recordTime;
    
    @JSONField(format = "yyyy-MM-dd")
    private Date createTime;
    
    @Column(name = "is_disabled")
    private boolean disabled;
    
    /**
     * The default constructor
     */
    public InbodyRecord() {
    }
    
    /**
     * 
     * @param user
     * @param inbodyData
     */
    public InbodyRecord(User user, InbodyData inbodyData) {
        this.user = user;
        this.name = user.getName();
        this.initialize(inbodyData);
        this.createTime = new Date();
        this.disabled = false;
    }
    
    public InbodyRecord(InbodyData inbodyData) {
        this.initialize(inbodyData);
        this.createTime = new Date();
        this.disabled = false;
    }
    
    public InbodyRecord initialize(InbodyData inbodyData) {
        this.source = inbodyData.getSource();
        
        if(StringUtils.isNoneEmpty(inbodyData.getSex()) && inbodyData.getSex().equalsIgnoreCase("F")) {
            this.gender = Gender.FEMALE;
        } else if (StringUtils.isNoneEmpty(inbodyData.getSex()) && inbodyData.getSex().equalsIgnoreCase("M")) {
            this.gender = Gender.MALE;
        }
        
        this.age = inbodyData.getAge();
        this.mobile = inbodyData.getMobile();
        this.weight = inbodyData.getWeight();
        this.weightMax = inbodyData.getWeightMax();
        this.weightMin = inbodyData.getWeightMin();
        this.sm = inbodyData.getSm();
        this.smMax = inbodyData.getSmMax();
        this.smMin = inbodyData.getSmMin();
        this.bf = inbodyData.getBf();
        this.bfMax = inbodyData.getBfMax();
        this.bfMin = inbodyData.getBfMin();
        this.bfr = inbodyData.getBfr();
        this.bfrMax = inbodyData.getBfrMax();
        this.bfrMin = inbodyData.getBfrMin();
        this.bmi = inbodyData.getBmi();
        this.bmiMax = inbodyData.getBmiMax();
        this.bmiMin = inbodyData.getBmiMin();
        this.whr = inbodyData.getWhr();
        this.whrMax = inbodyData.getWhrMax();
        this.whrMin = inbodyData.getWhrMin();
        this.bm = inbodyData.getBm();
        this.bmMax = inbodyData.getBmMax();
        this.bmMin = inbodyData.getBmMin();
        if(StringUtils.isNoneBlank(inbodyData.getRecordTime())) {
            this.recordTime = DateFormatUtils.format(DateUtils.parseDate(inbodyData.getRecordTime(), "yyyyMMddHHmmss"), "yyyy-MM-dd HH:mm:ss");
        }
        
        return this;
    }
   
    /**
     * 
     * @param user
     * @return
     */
    public InbodyRecord bindUser(User user) {
        
        this.user = user;
        this.name = user.getName();
        
        return this;
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getRecordMonthDay() {
        Date date = DateUtils.parseDate(this.recordTime, "yyyy-MM-dd HH:mm:ss");
        return DateFormatUtils.format(date, "MM-dd");
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public Date getRecordTimeDate() {
        return DateUtils.parseDate(this.recordTime, "yyyy-MM-dd HH:mm:ss");
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getWeightLabel() {
        if(this.weight > this.weightMax) {
            return "偏重";
        } else if (this.weight < this.weightMin){
            return "偏瘦";
        }else {
            return "正常";
        }
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getSmLabel() {
        if(this.sm > this.smMax) {
            return "偏多";
        } else if (this.sm < this.smMin){
            return "偏少";
        }else {
            return "正常";
        }
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getBfLabel() {
        if(this.bf > this.bfMax) {
            return "偏高";
        } else if (this.bf < this.bfMin){
            return "偏低";
        }else {
            return "正常";
        }
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getBfrLabel() {
        if(this.bfr > this.bfrMax) {
            return "偏高";
        } else if (this.bfr < this.bfrMin){
            return "偏低";
        }else {
            return "正常";
        }
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getBmiLabel() {
        if(this.bmi > this.bmiMax) {
            return "偏高";
        } else if (this.bmi < this.bmiMin){
            return "偏低";
        }else {
            return "正常";
        }
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getWhrLabel() {
        if (this.whr < this.whrMin){
            return "偏低";
        }else {
            return "正常";
        }
//        
//        if(this.whr > this.whrMax) {
//            return "偏高";
//        } else 
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public String getBmLabel() {
        if(this.bm > this.bmMax) {
            return "偏高";
        } else if (this.bm < this.bmMin){
            return "偏低";
        }else {
            return "正常";
        }
    }
    
    /**
     * @return the id
     */
    public Long getId() {
        return id;
    }

    /**
     * @return the user
     */
    public User getUser() {
        return user;
    }

    /**
     * @return the name
     */
    public String getName() {
        return name;
    }

    /**
     * @return the source
     */
    public String getSource() {
        return source;
    }

    /**
     * @return the age
     */
    public Integer getAge() {
        return age;
    }

    /**
     * @return the gender
     */
    public Gender getGender() {
        return gender;
    }

    /**
     * @return the mobile
     */
    public String getMobile() {
        return mobile;
    }

    /**
     * @return the weight
     */
    public Float getWeight() {
        return weight;
    }

    /**
     * @return the weightMax
     */
    public Float getWeightMax() {
        return weightMax;
    }

    /**
     * @return the weightMin
     */
    public Float getWeightMin() {
        return weightMin;
    }

    /**
     * @return the sm
     */
    public Float getSm() {
        return sm;
    }

    /**
     * @return the smMax
     */
    public Float getSmMax() {
        return smMax;
    }

    /**
     * @return the smMin
     */
    public Float getSmMin() {
        return smMin;
    }

    /**
     * @return the bf
     */
    public Float getBf() {
        return bf;
    }

    /**
     * @return the bfMax
     */
    public Float getBfMax() {
        return bfMax;
    }

    /**
     * @return the bfMin
     */
    public Float getBfMin() {
        return bfMin;
    }

    /**
     * @return the bfr
     */
    public Float getBfr() {
        return bfr;
    }

    /**
     * @return the bfrMax
     */
    public Float getBfrMax() {
        return bfrMax;
    }

    /**
     * @return the bfrMin
     */
    public Float getBfrMin() {
        return bfrMin;
    }

    /**
     * @return the bmi
     */
    public Float getBmi() {
        return bmi;
    }

    /**
     * @return the bmiMax
     */
    public Float getBmiMax() {
        return bmiMax;
    }

    /**
     * @return the bmiMin
     */
    public Float getBmiMin() {
        return bmiMin;
    }

    /**
     * @return the whr
     */
    public Float getWhr() {
        return whr;
    }

    /**
     * @return the whrMax
     */
    public Float getWhrMax() {
        return whrMax;
    }

    /**
     * @return the whrMin
     */
    public Float getWhrMin() {
        return whrMin;
    }

    /**
     * @return the bm
     */
    public Float getBm() {
        return bm;
    }

    /**
     * @return the bmMax
     */
    public Float getBmMax() {
        return bmMax;
    }

    /**
     * @return the bmMin
     */
    public Float getBmMin() {
        return bmMin;
    }

    /**
     * @return the recordTime
     */
    public String getRecordTime() {
        return recordTime;
    }

    /**
     * @return the createTime
     */
    public Date getCreateTime() {
        return createTime;
    }

    /**
     * @return the disabled
     */
    public boolean isDisabled() {
        return disabled;
    }

    /**
     * @param id the id to set
     */
    public void setId(Long id) {
        this.id = id;
    }

    /**
     * @param user the user to set
     */
    public void setUser(User user) {
        this.user = user;
    }

    /**
     * @param name the name to set
     */
    public void setName(String name) {
        this.name = name;
    }

    /**
     * @param source the source to set
     */
    public void setSource(String source) {
        this.source = source;
    }

    /**
     * @param age the age to set
     */
    public void setAge(Integer age) {
        this.age = age;
    }

    /**
     * @param gender the gender to set
     */
    public void setGender(Gender gender) {
        this.gender = gender;
    }

    /**
     * @param mobile the mobile to set
     */
    public void setMobile(String mobile) {
        this.mobile = mobile;
    }

    /**
     * @param weight the weight to set
     */
    public void setWeight(Float weight) {
        this.weight = weight;
    }

    /**
     * @param weightMax the weightMax to set
     */
    public void setWeightMax(Float weightMax) {
        this.weightMax = weightMax;
    }

    /**
     * @param weightMin the weightMin to set
     */
    public void setWeightMin(Float weightMin) {
        this.weightMin = weightMin;
    }

    /**
     * @param sm the sm to set
     */
    public void setSm(Float sm) {
        this.sm = sm;
    }

    /**
     * @param smMax the smMax to set
     */
    public void setSmMax(Float smMax) {
        this.smMax = smMax;
    }

    /**
     * @param smMin the smMin to set
     */
    public void setSmMin(Float smMin) {
        this.smMin = smMin;
    }

    /**
     * @param bf the bf to set
     */
    public void setBf(Float bf) {
        this.bf = bf;
    }

    /**
     * @param bfMax the bfMax to set
     */
    public void setBfMax(Float bfMax) {
        this.bfMax = bfMax;
    }

    /**
     * @param bfMin the bfMin to set
     */
    public void setBfMin(Float bfMin) {
        this.bfMin = bfMin;
    }

    /**
     * @param bfr the bfr to set
     */
    public void setBfr(Float bfr) {
        this.bfr = bfr;
    }

    /**
     * @param bfrMax the bfrMax to set
     */
    public void setBfrMax(Float bfrMax) {
        this.bfrMax = bfrMax;
    }

    /**
     * @param bfrMin the bfrMin to set
     */
    public void setBfrMin(Float bfrMin) {
        this.bfrMin = bfrMin;
    }

    /**
     * @param bmi the bmi to set
     */
    public void setBmi(Float bmi) {
        this.bmi = bmi;
    }

    /**
     * @param bmiMax the bmiMax to set
     */
    public void setBmiMax(Float bmiMax) {
        this.bmiMax = bmiMax;
    }

    /**
     * @param bmiMin the bmiMin to set
     */
    public void setBmiMin(Float bmiMin) {
        this.bmiMin = bmiMin;
    }

    /**
     * @param whr the whr to set
     */
    public void setWhr(Float whr) {
        this.whr = whr;
    }

    /**
     * @param whrMax the whrMax to set
     */
    public void setWhrMax(Float whrMax) {
        this.whrMax = whrMax;
    }

    /**
     * @param whrMin the whrMin to set
     */
    public void setWhrMin(Float whrMin) {
        this.whrMin = whrMin;
    }

    /**
     * @param bm the bm to set
     */
    public void setBm(Float bm) {
        this.bm = bm;
    }

    /**
     * @param bmMax the bmMax to set
     */
    public void setBmMax(Float bmMax) {
        this.bmMax = bmMax;
    }

    /**
     * @param bmMin the bmMin to set
     */
    public void setBmMin(Float bmMin) {
        this.bmMin = bmMin;
    }

    /**
     * @param recordTime the recordTime to set
     */
    public void setRecordTime(String recordTime) {
        this.recordTime = recordTime;
    }

    /**
     * @param createTime the createTime to set
     */
    public void setCreateTime(Date createTime) {
        this.createTime = createTime;
    }

    /**
     * @param disabled the disabled to set
     */
    public void setDisabled(boolean disabled) {
        this.disabled = disabled;
    }
}
